#ifndef AUTOTESTERENGINE_H_
#define AUTOTESTERENGINE_H_

#include <e32base.h>
#include <aknglobalnote.h>
#include <avkon.rsg>
#include <avkon.hrh>
#include <COEMAIN.H>
#include <APGWGNAM.H>
#include <APGTASK.H>
#include <APGCLI.H>
#include <apacmdln.h>
#include <stdio.h>
#include "CAutoTimer.h"
#include "SchedulerTimer.h"

#define MAX_HANDLES 25

typedef struct _KeyData
{
	TUint 		iTimeSec;
	TInt 		iScanCode;
	TUint 		iCode;
	TUint 		iModifiers;
	TInt 		iRepeats;
	TUint 		iWg;
	_KeyData(): iTimeSec(0), iScanCode(0), iCode(0), iModifiers(0), iRepeats(0), iWg(0)
	{}
} KeyData;

class CAutoTester : public CActive
{
	public:
		/**
		 * Starts the application
		 * */
		void Start();
		
		/**
		 * Stops the application
		 * */
		void Stop();
		
		/**
		 * Replays the captured events
		 * */
		void Replay();
		
		/**
		 * Saves the generated events to a CSV file
		 * */
		void SaveEvents();
		
		/**
		 * Reloads the generated events from a CSV file
		 * */
		void ReloadEvents();
		
		/**
		 * Schedules a replay of the events
		 * */
		void ScheduleReplay(TUint aHours);
		
		/**
		 * Destructor
		 * */
		~CAutoTester();
		
		/**
		 * Returns the sole instance of the class
		 * */
		static CAutoTester* GetInstance();
		
		/**
		 * Stores the generated event to the array
		 * */
		void StoreKeyEvent(TUint& aCode, TInt& aScanCode, TUint& aModifiers, TInt& aRepeats, TUint& aWg);
		
		/**
		 * Returns the value of the bool indicating if the keys are being captured 
		 * */
		TBool IsCapturing();
		
		/**
		 * The function simulates the key at the index of the event array
		 * */
		bool SimulateKeyEvent(TUint aIndex);
		
		/**
		 * Returns the time difference to be used before generating next event 
		 * */
		TUint GetNextTimeDifference(TUint aIndex);
		
		/**
		 * Sets the value of the replaying boolean
		 * */
		void SetReplaying(TBool aValue);
		
		/**
		 * Returns the number of events in the array
		 * */
		TUint GetArrayCount();
		
	private:
		/**
		 * Function that is called when a key is pressed
		 * */
		void RunL();
		
		/**
		 * Cancels any pending requests
		 * */
		void DoCancel();
		
		/**
		 * Starts the key capturing process
		 * */
		void StartCapturingL();
		
		/**
		 * Stops the key capturing process
		 * */
		void StopCapturing();
		
		/**
		 * Constructor
		 * */
		CAutoTester();
		
		/**
		 * Function to create the object of the engine
		 * */
		static CAutoTester* NewL();
		
		/**
		 * Second level constructor
		 * */
		void ConstructL();
		
		/**
		 * Simulate key using the RawEvent method
		 * */
		void SimulateKey(TInt& aScanCode);
		
		/**
		 * Simulate key using the "SendToWindowGroup" method
		 * */
		void SimulateKey(TUint& aCode, TInt& aScanCode, TUint& aModifiers, TInt& aRepeats, TUint& aWg);
		
		/**
		 * Simulate key using the direct simulation method
		 * */
		void SimulateKey(TUint& aCode, TInt& aScanCode, TUint& aModifiers, TInt& aRepeats);
		
		/**
		 * Launches the "Telephone" application
		 * */	
		void LaunchAppL(const TUid aAppUid);
		
		/**
		 * Brings the device's main screen to the foreground
		 * */
		void BringDesktopToForegroud();
		
		/**
		 * Creates the environment required for key simulation / replay
		 * */
		void CreateSimulationEnv();
		
	private:
		TBool 				iCapturing; /** boolean value which controls the recording of the events */
		TBool 				iReplaying; /** boolean indicating replay is in progress */ 
		TBool 				iScheduled; /** boolean indicating replay is scheduled */
		TBool				iArrayEmpty; /** boolean */
		RArray<KeyData> 	iKeyData; /** array storing the captured events */
		
		RWsSession     		iWsSession; /** Window server session */
		RWindowGroup    	iWindowGroup; /** Window group object */
		
		static CAutoTester* self; /** pointer to the sole instance of the class (SINGLETON DESIGN PATTERN) */
		
		TInt 				iHandles[MAX_HANDLES]; /** handles of the keys being captured */
		TUint 				iHandlesCount; /** maximum handles the application can handle */
		TUint 				iItemCount; /** count of the capured events */
		
		CAutoTimer* 		iTimer; /** timer used to simulate the time difference between key presses during replay */
		CSchedulerTimer* 	iSchedulerTimer; /** timer used to replay the events after a certain time interval */
};

#endif /*AUTOTESTERENGINE_H_*/
